package it.luigiarpino.kernighanLin;



public class LinKernighanAmmissibile 
{

	
	private int[] partizionamento;
	private int costo;
	private int costoMaxTaglio;
	private int numMaxNodiPerPartizione;
	private int numeroEsecuzioni;
	
	/**
	 * 
	 * @param matrix
	 * @param numeroPartizioni numero di partizioni che compongono il grafo
	 * @param taglioMax il valore del taglio massimo
	 * @param maxNodi il numero massimo di nodi che possono far parte della stessa partizione
	 * @throws LinKernighanException 
	 */
	public LinKernighanAmmissibile(int[][]matrice,  int taglioMax, int maxNodi) throws LinKernighanException
	{
		boolean isFisrtCycle=true;
		this.costo =0;
		this.numeroEsecuzioni=-1;
		for (int i=0; i< 5; i++)
		{
			LinKernighan kpart=new LinKernighan(matrice, maxNodi);
			int costoAttuale=kpart.getCosto();
			int costoMaxTaglioAttuale= kpart.getCostoMaxTaglio();
			int numNodi=kpart.getNumMaxNodiPerPartizione();
			if (isFisrtCycle || ((costoAttuale<costo)&&(costoMaxTaglioAttuale <= taglioMax)&&( numNodi<=maxNodi)) )
			//if (isFisrtCycle || ((costoAttuale<costo)&&(costoMaxTaglioAttuale < taglioMax)&&( numNodi<maxNodi)) )
			{
				isFisrtCycle=false;
				this.numeroEsecuzioni=i;
				this.costo=costoAttuale;
				this.partizionamento=kpart.getPartizionamento();
				this.costoMaxTaglio=kpart.getCostoMaxTaglio();
				this.numMaxNodiPerPartizione=kpart.getNumMaxNodiPerPartizione();
			}
		}
		if (this.costoMaxTaglio>taglioMax || this.numMaxNodiPerPartizione>maxNodi)
		{
			throw new LinKernighanException("Nessuna soluzione ammissibile!");
		}
		this.numeroEsecuzioni ++;
	}
	
	/**
	 * Restituisce il numero di esecuzione richieste
	 * pertrovare la soluzione ottimale
	 * 
	 * @return
	 */
	public int getNumeroEsecuzioni()
	{
		return this.numeroEsecuzioni;
	}
	
	public int getCosto() 
	{
		return costo;
	}

	public int getCostoMaxTaglio()
	{
		return this.costoMaxTaglio;
	}
	
	public int[] getPartizionamento() 
	{
		return partizionamento;
	}
	
	public int getNumMaxNodiPerPartizione()
	{
		return this.numMaxNodiPerPartizione;
	}
	
	public static void main(String[] args) throws LinKernighanException
	{
		int[][] matrix={
			    //   0  1  2  3 
					{0, 1, 1, 1},// 0
					{1, 0, 0, 0},// 1
					{1, 0, 0, 0},// 2
					{1, 0, 0, 0},// 3
			};
		int taglioMax=100;
		int maxNodi=3;
		LinKernighanAmmissibile lk=new LinKernighanAmmissibile(matrix,  taglioMax, maxNodi);
		int costo=lk.getCosto();
		int[] partizionamento = lk.getPartizionamento();
		System.out.println();
		System.out.println("Costo="+costo);
		System.out.println();
		for(int i=0; i< partizionamento.length ; i++)
	    {
			System.out.print(" "+partizionamento[i]);
	    }
	}
	
}
